import java.util.ArrayList;
import java.util.LinkedList;
import java.util.List;
import java.util.Queue;
import java.util.Random;

public class Reader implements Runnable, IReader 
{
	
	//private String name;
	private Queue<BookLend> activeLends = new LinkedList<BookLend>();
	private final Library library;
	private Random rand = new Random();
	private boolean isLate = false;
	private boolean onBookFound = false;
	List<Book> lastSearch;
	public String name;
	
	public Reader(Library library, String name) 
	{
		this.library = library;
		this.library.registerReader(this);
		this.name = name;
	}

	private void getBook() 
	{
		ILibraryStaff servitor;
		try {
			servitor = library.getFreeLibraryStaff();
			List<BookQuery> bq = new ArrayList<BookQuery>();
			int num = rand.nextInt(3) +1;
			StringBuilder printQuery = new StringBuilder();
			for(int i = 0; i < 1 + num; i++) {
				BookQuery query = Store.getRandomQuery();
				bq.add(query);
				printQuery.append(query);
				printQuery.append(" AND ");
			}
			servitor.searchForBook(this, bq);
			System.out.println("I [" + name + "] interested in " + printQuery.toString());
		} catch (InterruptedException e) 
		{
			e.printStackTrace();
		}
	}
	
	private void readBookInLibrary() 
	{
		//to do:
	}

	private void returnBook() 
	{
		ILibraryStaff servitor;
		try 
		{
			servitor = library.getFreeLibraryStaff();
			servitor.bookReturn(this, activeLends.remove());
			// readingNow = null;
		} catch (InterruptedException e) { e.printStackTrace(); }

	}
	
	private void takeBooks()
	{
		ILibraryStaff servitor;
		try
		{
			servitor = library.getFreeLibraryStaff();
			int num = lastSearch.size() % 4 + 1;
			List<Book> selected =  Store.getRandomBooks(lastSearch,num);
			servitor.bookRetrieval(this, selected);
			StringBuilder books = new StringBuilder();
			for (Book book: selected) {
				books.append(book);
			}
			System.out.println("I, the reader [" + name + "] , am trying" + books.toString());
		}
		catch(InterruptedException e) { e.printStackTrace(); }
	}

	public void run() 
	{
		while (true) 
		{
			try
			{
				
				if (!library.isOpen()) 
				{
					System.out.println("go HOME and come back later...");
					Thread.sleep(2500);
					continue;
				}
				if(isLate)
				{
					returnBook();
					isLate = false;
				}
				if(onBookFound)
				{
					takeBooks();
					lastSearch = null;
					onBookFound = false;
				}
				if (rand.nextInt() % 3 == 0) 
				{
					getBook(); 
					//Thread.sleep();
				}
				if (activeLends.size() > 0 && activeLends.peek().getReturnDays() < rand.nextInt(8) + 1)
				{
					returnBook();
				}
				Thread.sleep(1000);
			} 
			catch (InterruptedException e) { e.printStackTrace(); }

		}
	}

	@Override
	public void onBooksFound(List<Book> books)
	{
		//xaresva si 4ast ot knigite i iska da gi vzeme....
		onBookFound = true;
		lastSearch = books;
	}

	@Override
	public void onBooksLend(BookLend books) 
	{
		if (books != null) {
			System.out.println("I, the reader [" + name + "]" + "have taken successfuly the books");
			activeLends.add(books);
		} else {
			System.out.println("There aren't any books left or I have taken the maximum     [" + name + "]");
		}
	}
	
	@Override
	//public void onBookReturn(BookLend books) 
	public void onBookReturn(boolean b)
	{
		//activeLends.remove(books);
		if(b) System.out.println("I the reader [" + name + "] have returned books succesfully");
		else System.out.println("I the reader [" + name + "] have not returned books succesfully");
	}

	@Override
	public void onBookLate(BookLend books) 
	{
		isLate = true;
	}

}
